複数行に打ち消し線を引くPopup Menu その2
突貫工事でやってみたけど、意外と一筋縄では行かない
上位のnodeに文字装飾記法がないときだけ、-で囲むようにしないと、リンクが出来てしまう
Gyazoの画像がリンクに変換されてしまう
Gyazoのサムネイル画像を検出して、それをGyazoのpermalinkに変換する処理を入れる必要がある
打ち消し記法がかなり細かくなってしまう
隣にリンクやplain textがあるときは、まとめて打消し線を引けるように変えるべきだが、flag処理とか色々やる必要が出てきそう
変換する必要のない記法に対する処理も書かなくてはいけない
「元に戻す」処理を書く
dependencies
code:script.js
import {ScrapboxParser} from '../scrapbox-parser.min.js/parser.js';
scrapbox.PopupMenu.addButton({
title: '\uf0cc',
onClick: text => {
const result = convert(text);
if (text === result) return; // 変更がなければ何もしない
return result;
},
});
変換する関数
code:script.js
function convert(text) {
const blocks = ScrapboxParser.parse(text, {hasTitle: false});
return blocks.flatMap(block => {
switch (block.type) {
case 'title':
return [];
case 'codeBlock':
return convertCodeBlock(block);
case 'table':
return convertTable(block);
case 'line':
return convertLine(block);
}
})
.map((line, i) => ${' '.repeat(blocks[i].indent)}${line})
.join('\n');
}
function convertCodeBlock({fileName, content}) {
return [code:${fileName}, ...content.split('\n').map(line => ${line})];
}
function convertTable({fileName, cells}) {
return [table:${fileName}, ...cells.map(cell => ${cell.map(([{text}]) => text).join('\t')}),];
}
function convertLine({nodes}) {
return [nodes.map(node => ${' '.repeat(node.indent)}${convertNode(node)}).join('')];
}
function convertNode(node, noStrike) {
switch (node.type) {
case 'quote':
return > ${node.nodes.map(node => convertNode(node)).join('')};
case 'helpfeel':
return [${noStrike ? '' : '- '}? ${node.text}];
case 'image':
return [${node.src}${node.link ? ${node.link} : ''}];
case 'strongImage':
return [[${node.src}${node.link ? ${node.link} : ''}]];
case 'icon':
return [${node.path}.icon];
case 'strongIcon':
return [[${node.path}.icon]];
case 'strong':
return [[${node.nodes.map(node => convertNode(node)).join('')}]];
case 'formula':
return [$ ${node.formula}];
case 'decoration':
if (!node.decos.includes('-')) node.decos.push('-');
const deco = node.decos.map(deco => {
if (/\*-/.test(deco)) {
const num = deco.match(/\*-(\d)/)1; return '*'.repeat(num);
}
return deco;
}).join('');
return [${deco ? ${deco} : ''}${node.nodes.map(node => convertNode(node, deco.includes('-'))).join('')}];
case 'code':
return \`${node.text}\`;
case 'commandLine':
return [${noStrike ? '' : '- '}${node.symbol} ${node.text}];
case 'link':
switch(node.pathType) {
case 'root':
case 'relative':
return [${noStrike ? '' : '- '}[${node.href}]];
case 'absolute':
return [${noStrike ? '' : '- '}[${node.content ? ${node.content} : ''}${node.href}]];
}
case 'googleMap':
return [N${node.latitude},E${node.longitude},Z${node.zoom} ${node.place}];
case 'hashTag':
return [${noStrike ? '' : '- '}#${node.href}];
case 'blank':
case 'plain':
return noStrike ? node.text :[- ${node.text}];
}
}